// step1
const http = require("http")
const request = require('./request')
const response = require('./response')
const context = require('./context')

// let request = {
//     get url(){
//       console.log(this)
//       return this.req.url
//     }
// }
//
// let response = {
//     get body(){
//         return this.res.body
//     },
//     set body(value){
//         this.res.body = value
//     }
// }
//
// let context = {
//     get url(){
//         return this.request.url
//     },
//     get body(){
//         return this.response.body
//     },
//     set body(value){
//         this.response.body = value
//     }
// }

class Application {
  constructor() {
    this.middleWares=[]
    this.context = context
    this.request = request
    this.response = response
  }
  createCtx(req,res) {
    let ctx = Object.create(this.context)
    ctx.request = Object.create(this.request)
    ctx.response = Object.create(this.response)
    ctx.req = ctx.response.req = req
    ctx.res = ctx.response.res = res
    return ctx
  }
  use(callback){
    // this.callback = callback
    this.middleWares.push(callback)
    return this;
  }
  compose(ctx, middlewares){
     async function dispatch(index){
       if(index === middlewares.length) return;
       let fn = middlewares[index]
       return await fn(ctx,() => dispatch(index + 1));
     }
     return dispatch(0)
  }
  listen(...args){
    let server = http.createServer(async(req,res) => {
      let ctx = this.createCtx(req,res)
      this.compose(ctx, this.middleWares).then(() => {
        res.end(ctx.body)
      }).catch(err=>{
        console.log(err)
      })
    });
    server.listen(...args)
  }
}
module.exports = Application
